/*                          UX-Framework                               
 *                                                                 
 *  iZE Co.,Ltd. Copyright 2009 All rights reserved.          
 *  This file is distributed under the terms of the GNU Lesser 
 *  General Public License, described in file LICENSE.                                     
 */
package jp.ize.ux;

// {{{ imports
#if flash9
import flash.events.Event;
import flash.events.FocusEvent;
#elseif flash
#end

import jp.ize.ux.filters.UXFilter;
import jp.ize.ux.UXFocusManager;
// }}}
// {{{ enum BlendMode
enum BlendMode
{
	/** Zオーダーが大きい方が不透明度100%で表示される、通常の重なり方です. */
	NORMAL;
	LAYER;       /* */
	MULTIPLY;    /* */
	SCREEN;      /* */
	LIGHTEN;     /* */
	DARKEN;      /* */
	DIFFERENCE;  /* */
	ADD;         /* */
	SUBTRACT;    /* */
	INVERT;      /* */
	ALPHA;       /* */
	ERASE;       /* */
	OVERLAY;     /* */
	HARDLIGHT;   /* */
}
// }}}
// {{{ class UXObject extends XXObj
/** 
 * UXObjectクラス.<br>
 * UX-Frameworkの基礎となるクラス。基礎的な描画プロパティ、コンテナ機能、テーマ機能、フォーカス機能、
 * イベント機能などを持ちます。<br>
 *
 * @author		iZE Co., Ltd.<br>
 * @version		$Id: UXObject.hx 160 2009-05-01 06:19:45Z tocy.net $<br>
 */
class UXObject extends XXObj
{
	// {{{ properties

	// プライベート変数
	var _focusManager : UXFocusManager;

	// }}}
	// {{{ public var name(default, default) : String
	/**
	 * このコンポーネントの名前です。主にユーザーのアクティビティを観察・保存する際にコンポーネントの識別子として用いられます。
	 */
	public var name(default, default) : String;
	// }}}
	// {{{ public var x(getX, setX) : Float;
	/**
	 * 親コンテナからの相対X座標位置を示します。
	 */
	public var x(getX, setX) : Float;
	// }}}
	// {{{ public var y(getY, setY) : Float;
	/**
	 * 親コンテナからの相対Y座標位置を示します。
	 */
	public var y(getY, setY) : Float;
	//}}}
	#if flash10
	// {{{ public var z(getZ, setZ) : Float
	/**
	 * 親コンテナからの相対Z座標位置を示します。
	 */
	public var z(getZ, setZ) : Float;
	// }}}
	// {{{ public var rotationX( getRotationX, setRotationX ) : Float;
	/**
	 * 親コンテナを基準にしたx軸に対する回転角度を度数単位で示します。
	 */
	public var rotationX( getRotationX, setRotationX ) : Float;
	// }}}
	// {{{ public var rotationY( getRotationY, setRotationY ) : Float;
	/**
	 * 親コンテナを基準にしたz軸に対する回転角度を度数単位で示します。
	 */
	public var rotationY( getRotationY, setRotationY ) : Float;
	// }}}
	// {{{ public var rotationZ( getRotationZ, setRotationZ ) : Float;
	/**
	 * 親コンテナを基準にしたz軸に対する回転角度を度数単位で示します。
	 */
	public var rotationZ( getRotationZ, setRotationZ ) : Float;
	// }}}
	#end	
	// {{{ public var matrix(default, null) : Matrix;
	/**
	 * logical座標系から表示座標系への変換行列を示します。
	 */
	public var matrix(getMatrix, null) : UXMatrix;
	//}}}
	// {{{ public var width(getWidth, setWidth) : Float;
	/**
	 * オブジェクトの幅を示します。
	 */
	public var width(getWidth, setWidth) : Float;
	//}}}
	// {{{ public var height(getHeight, setHeight) : Float;
	/**
	 * オブジェクトの高さを示します。
	 */
	public var height(getHeight, setHeight) : Float;
	//}}}
	// {{{ public var followMatrix(default, null) : Bool;	
	/**
	 * オブジェクトの大きさに拡大率を追従させるかどうかを示します。デフォルトでfalseです。
	 */
	public var followMatrix(default, null) : Bool;
	//}}}
	// {{{ public var layoutSize(default, default) : UXSize;
	/**
	 * レイアウト領域を示します。nullの場合はこのオブジェクトのwidth, height情報で表されるサイズがレイアウト領域になります。
	 */
	public var layoutSize(default, default) : UXSize;
	//}}}
	// {{{ public var alpha : Float
	/**
	 * 透明度を示します。
	 */
	public var alpha(default, default) : Float;
	// }}}
	// {{{ public var sizeHint(default, default) : UXSizeHint
	/**
	 * このコンポーネントがレイアウトクラスによって配置される時に、このコンポーネントの大きさを制御する情報です。
	 * 詳細はUXSizeHintクラスを参照してください。
	 */
	public var sizeHint(default, default) : UXSizeHint;
	// }}}
	// {{{ public var blend(default, default) : BlendMode
	/**
	 * コンポーネント同士が重なった場所のピクセル演算を定義します。詳細はBlendModeを参照してください。
	 */
	public var blend(default, default) : BlendMode;
	// }}}
	// {{{ public var focusIndex(default, default) : Int
	/**
	 * フォーカスが移動する順番を規定する数値。絶対値に意味は無く、UXFocusManagerの同一インスタンスに登録されているUXObject同士のfocusIndexの大小が意味を持ちます。
	 */
	public var focusIndex(default, default) : Int;
	// }}}	
	// {{{ public var graphics(default, null) : UXGraphics;
	/**
	 * このオブジェクトを表示するためのUXGraphicsオブジェクトを指定します。
	 */
	public var graphics(default, null) : UXGraphics;
	// }}}
	// {{{ public function new()
	/**
	 * コンストラクタ
	 */
	public function new()
	{
		super();
		this.graphics = new UXGraphics(sprite.graphics);
	}
	// }}}
	// {{{ private function getX() : Float
	/**
	 * 親コンテナの相対X座標位置を返します。
	 */
	public function getX() : Float
	{
		return sprite.x;
	}
	// }}}
	// {{{ private function setX( x : Float ) : Void
	/**
	 * 親コンテナの相対X座標位置を設定します。
	 */
	public function setX( x : Float ) : Float
	{
		sprite.x = x;
		return x;
	}
	// }}}
	// {{{ private function getY() : Float
	/**
	 * 親コンテナの相対Y座標位置を返します。
	 */
	public function getY() : Float
	{
		return sprite.y;
	}
	// }}}
	// {{{ private function setY( y : Float ) : Void
	/**
	 * 親コンテナの相対Y座標位置を設定します。
	 */
	public function setY( y : Float ) : Float
	{
		sprite.y = y;
		return y;
	}
	// }}}
	#if flash10
	// {{{ private function getZ() : Float
	/**
	 * 親コンテナの相対Z座標位置を返します。
	 */
	public function getZ() : Float
	{
		return sprite.z;
	}
	// }}}
	// {{{ private function setZ( z : Float ) : Void
	/**
	 * 親コンテナの相対Z座標位置を設定します。
	 */
	public function setZ( z : Float ) : Float
	{
		sprite.z = z;
		return z;
	}
	// }}}
	// {{{ properties

	public function getRotationX() return sprite.rotationX
	public function setRotationX(rx) return sprite.rotationX = rx
	public function getRotationY() return sprite.rotationY
	public function setRotationY(ry) return sprite.rotationY = ry
	public function getRotationZ() return sprite.rotationZ
	public function setRotationZ(rz) return sprite.rotationZ = rz

	// }}}
	#end
	// {{{ public function getMatrix() : UXMatrix
	/**
	 * logical座標系から表示座標系への変換行列を返します。
	 */
	public function getMatrix() : UXMatrix
	{
		return null;
	}
	// }}}
	// {{{ private function getWidth() : Float
	/**
	 * オブジェクトの幅を返します。
	 */
	public function getWidth() : Float
	{
		return sprite.width;
	}
	// }}}
	// {{{ private function setWidth( w : Float ) : Float
	/**
	 * オブジェクトの幅を設定します。
	 * followMatrix が true のときは matrix の拡大率を追従させます。
	 */
	public function setWidth( w : Float ) : Float
	{
		return w;
	}
	// }}}
	// {{{ private function getHeight() : Float
	/**
	 * オブジェクトの高さを返します。
	 */
	public function getHeight() : Float
	{
		return sprite.height;
	}
	// }}}
	// {{{ private function setHeight( h : Float ) : Float
	/**
	 * オブジェクトの高さを示します。
	 */
	public function setHeight( h : Float ) : Float
	{
		sprite.height = h;
		return h;
	}
	// }}}
	// {{{ public function addEventListener( type : String, l : Dynamic -> Void ) : Void
	/**
	 * イベントリスナーを登録し、リスナーがイベントの発動を受けとるようにします。
	 */
 	public function addEventListener( name : String, listener : UXEvent -> Void ) : Void
	{
		// just sample.
		var l = function( fe ) return listener( XXObj.flashEvent2UXEvent( fe ) );
		sprite.addEventListener( XXObj.event2FlashEvent(name), l);
	}
	// }}}
	// {{{ public function removeEventLisntener( type : String ) : Void
	/**
	 * イベントリスナーを削除します。
	 */
	public function removeEventLisntener( type : String ) : Void
	{
	}
	// }}}
	// {{{ public function putEvent( event : Event ) : Bool
	/**
	 * 指定されたイベントをこのオブジェクトに配信します。
	 */
	#if flash9
	public function putEvent( event : Event ) : Bool
	#elseif flash
	public function putEvent( event : Dynamic ) : Bool
	#end
	{
		return true;
	}
	// }}}
	// {{{ public function addFilter( filter : UXFilter ) : Void
	/**
	 * 指定されたフィルターをこのコンポーネントに適用します。
	 */
	public function addFilter( filter : UXFilter ) : Void
	{
	}
	// }}}
	// {{{ public function removeFilter( filter : UXFilter ) : Void
	/**
	 * 指定されたフィルターをこのこのコンポーネントから削除します。指定されたフィルターが見つからない場合は何もしません。
	 */
	public function removeFilter( filter : UXFilter ) : Void
	{
	}
	// }}}
	// {{{ public function clearFilter() : Void
	/**
	 * このコンポーネントに適用されている全てのフィルターを削除します。
	 */
	public function clearFilter() : Void
	{
	}
	// }}}
	// {{{ public function setFocusManager( m : UXFocusManager ) : Void
	/**
	 * このオブジェクトのフォーカスを管理するマネージャーを得ます。フォーカス関連の操作を行う前に、この関数を呼び出しておく必要があります。
	 */
	public function setFocusManager( m : UXFocusManager ) : Void
	{
	}
	// }}}
	// {{{ public function focus( ?mode : UXFocusHint ) : Void
	/**
	 * このオブジェクトにフォーカスを当てます。このオブジェクトがUXFocusMangerのインスタンスを持っていなければ、何もしません。
	 */
	public function focus() : Void
	{
	}
	// }}}
	#if flash9
	// {{{ private function onKeyFocusChange( e : FocusEvent ) : Void
	/**
	 * フォーカスがキーボードイベントによって移動する前に呼ばれるイベントです。
	 * フォーカスマネージャーからのイベントは特別に素通し、通常のイベントはフォーカスマネージャーに転送します。
	 */
	private function onKeyFocusChange( e : FocusEvent ) : Void
	{
		/* UXFocusEventにはhintフィールドがあるはず */
		var hint : String = Reflect.field(e, "hint");
		if( hint != null ) {
			/* 素通し */
		} else {
			/* 通常のFocusEventだと判断. */
			e.preventDefault (); /* フォーカスの移動を止めます. */
			if( _focusManager != null) {
				/* フォーカスマネージャーに依頼します. */
				if( e.shiftKey ) {
					_focusManager.previous(); 
				} else {
					_focusManager.next();
				}
			}
		}
	}
	// }}}
	// {{{ public function onMouseFocusChange( e : FocusEvent ) : Void
	/**
	 * フォーカスがマウスイベントによって移動する前に呼ばれるイベントです。
	 * フォーカスマネージャーからのイベントは特別に素通し、通常のイベントはフォーカスマネージャーに転送します。
	 */
	public function onMouseFocusChange( e : FocusEvent ) : Void
	{
		/* UXFocusEventにはhintフィールドがあるはず */
		var hint : String = Reflect.field(e, "hint");
		if( hint != null ) {
			/* 素通し */
		} else {
			/* 通常のFocusEventだと判断. */
			e.preventDefault (); /* フォーカスの移動を止めます. */
			if( _focusManager != null) {
				/* フォーカスマネージャーに依頼します. */
				var obj : UXObject = Reflect.field( e.relatedObject, "xxobj" );
				if( obj != null ) {
					_focusManager.setFocus( obj );
				}
			}
		}
	}
	// }}}
	#end
}
// }}}
